<?php
/**
 * Created by PhpStorm.
 * Script Name: Msg.php
 * Create: 2020/6/10 17:23
 * Description: 粉丝消息
 * Author: fudaoji<fdj@kuryun.cn>
 */

namespace plugin\wechat\app\tenant\controller;

use plugin\wechat\app\model\MpFollow;
use plugin\wechat\app\model\MpMsg as MsgM;
use plugin\wechat\app\model\MpRule as RuleM;
use plugin\wechat\app\model\MpMaterial as MaterialM;
use plugin\wechat\app\platform\handler\mp\MessageObj;
use plugin\wechat\app\service\Mp as MpService;
use plugin\wechat\app\TenantController;
use think\db\exception\DbException;
use think\db\exception\ModelNotFoundException;
use Support\Request;
use app\common\service\Upload;

class Mpmsg extends TenantController
{
    /**
     * @var  MsgM
     */
    protected $model;
    /**
     * @var  RuleM
     */
    private $ruleM;
    /**
     * @var MpFollow
     */
    private MpFollow $followM;

    public function __construct()
    {
        parent::__construct(); // TODO: Change the autogenerated stub
        $this->model = new MsgM();
        $this->ruleM = new RuleM();
        $this->followM = new MpFollow();
    }

    /**
     * 聊天详情
     * @param Request $request
     * @return mixed|\support\Response
     * @throws DbException
     * @throws ModelNotFoundException
     * @throws \EasyWeChat\Kernel\Exceptions\InvalidArgumentException
     * @throws \EasyWeChat\Kernel\Exceptions\InvalidConfigException
     * @throws \EasyWeChat\Kernel\Exceptions\RuntimeException
     * @throws \think\db\exception\DataNotFoundException
     * Author: fudaoji<fdj@kuryun.cn>
     */
    public function detail(Request $request){
        $mp_info = $request->mpInfo;
        if($mp_info['verify_type_info'] < 0 && $mp_info['service_type_info'] != 2){
            return $this->error('当前公众号未获取发送客服消息接口');
        }
        $openid = input('openid', '');
        $follow = $this->followM->where([
            $this->tenantWhere(),
            ['openid', '=', $openid],
            ['mp_id','=', $mp_info['id']]
        ])->find();
        if(request()->isPost()){
            $post_data = input('post.');
            if(!empty($post_data['media_type']) && !empty($post_data['media_id'])){
                $media_type = $post_data['media_type'];
                $media = MaterialM::where([
                    $this->tenantWhere(),
                    ['mp_id','=', $mp_info['id']],
                    ['id', '=', $post_data['media_id']],
                ])->find();
                $message = MessageObj::$media_type($media);
                $last_msg = $this->model->where([
                    $this->tenantWhere(),
                    ['mp_id','=', $mp_info['id']],
                    ['openid', '=', $openid],
                    ['is_reply', '=', 0],
                ])->order(['id' => 'desc'])->find();
                if(strtotime($last_msg['create_time']) - time() > (48 * 3600 - 60)){
                    return $this->error('与粉丝已经超过48小时没有互动了，无法主动发送消息', '', ['token' => token()]);
                }
                if(is_string($res = MpService::customerServiceMessageSend($message, $openid))){ //客服发送消息
                    return $this->error('回复失败，请刷新重试', '', ['token' => token()]);
                }
                //入库
                $media_array = $message->toXmlArray();
                if($media_type == 'text'){
                    $content = $media_array;
                }else{
                    $content = $media_array[ucfirst($media_type)];
                    $content['url'] = $media['url'];
                }
                $this->model->create([
                    'company_id' => $mp_info['company_id'],
                    'pid' => $last_msg['id'],
                    'openid' => $openid,
                    'mp_id' => $mp_info['id'],
                    'type' => $media_type,
                    'is_reply' => 1,
                    'content' => json_encode($content, JSON_UNESCAPED_UNICODE),
                    'nickname' => $mp_info['nick_name'],
                    'headimgurl' => $mp_info['head_img']
                ]);
                $this->model->update([
                    'id' => $last_msg['id'],
                    'company_id' => $mp_info['company_id'],
                    'status' => 1
                ]);
                return $this->success('回复成功', url('detail', ['openid' => $openid]));
            }
        }

        $where = [
            $this->tenantWhere(),
            ['mp_id','=', $mp_info['id']]
        ];
        $types = MpService::replyTypes();
        $msg_ids = $this->model->where([
            $this->tenantWhere(),
            ['openid', '=', $openid],
            ['mp_id','=', $mp_info['id']]
        ])->column('id');
        $where[] = ['id|pid', 'in', $msg_ids];
        $data_list = $this->model->page(1, 20)
        ->where($where)
            ->order('id','desc')
        ->select();
        foreach ($data_list as $k  => $value){
            $value['content'] = json_decode($value['content'], true);
            $data_list[$k] = $value;
        }
        $assign = [
            'data_list' => $data_list,
            'types' => $types
        ];
        $builder = new FormBuilder();
        $builder->setTemplate('mpmsg/detail')
            ->addFormItem('title', 'legend', '与'.$follow['nickname'].'的聊天', '')
            ->addFormItem('media', 'choose_wx_media', '回复类型', '回复类型', ['types' => $types], 'required')
        ->setBtnReset(['show' => false]);
        return $builder->show($assign);
    }

    /**
     * 消息列表
     * @param Request $request
     * @return mixed
     * Author: fudaoji<fdj@kuryun.cn>
     * @throws \think\db\exception\DataNotFoundException
     * @throws DbException
     * @throws ModelNotFoundException
     */
    public function index(Request $request){
        $mp_info = $request->mpInfo;
        $where = [
            $this->tenantWhere(),
            ['mp_id', '=', $mp_info['id']],
            ['is_reply', '=', 0]
        ];
        $search_key = input('search_key', '');
        $search_key && $where[] = ['content', 'like', '%'.$search_key.'%'];
        $types = MpService::replyTypes();

        $data_list = $this->model->where($where)
            ->order('id', 'desc')
            ->paginate($this->pageSize);
        foreach ($data_list as $k  => $value){
            $value['content'] = json_decode($value['content'], true);
            $data_list[$k] = $value;
        }
        $page = $data_list->appends(['search_key' => $search_key])->render();
        $assign = [
            'data_list' => $data_list,
            'page' => $page,
            'search_key' => $search_key,
            'types' => $types
        ];
        return $this->show($assign);
    }


    /**
     * 获取临时素材链接
     * @param Request $request
     * @return \support\Response
     * @throws \EasyWeChat\Kernel\Exceptions\InvalidArgumentException
     * @throws \EasyWeChat\Kernel\Exceptions\InvalidConfigException
     * @throws \EasyWeChat\Kernel\Exceptions\RuntimeException
     * @throws \GuzzleHttp\Exception\GuzzleException
     * @throws \think\db\exception\DataNotFoundException
     * @throws DbException
     * @throws ModelNotFoundException
     * @author: fudaoji<fdj@kuryun.cn>
     */
    public function getTempMediaUrlPost(Request $request){
        $mp_info = $request->mpInfo;

        if(request()->isPost()){
            $media_id = input('media_id', '');
            $id = input('id', '');
            $msg = $this->model->where([
                ['id' ,'=', $id],
                $this->tenantWhere(),
                ['mp_id', '=', $mp_info['id']],
            ])->find();
            $content = json_decode($msg['content'], true);
            if(!empty($content['url'])){ //说明已经处理过
                return $this->success('从数据库获取的', '', ['url' => $content['url']]);
            }
            if($material = MaterialM::where([$this->tenantWhere(), ['media_id','=', $media_id]])->find()){
                $content['url'] = $material['server_url'];
            }else{
                $stream = MpService::mediaGet(['media_id' => $media_id]);
                if($stream instanceof \EasyWeChat\Kernel\Http\StreamResponse){
                    $upload_path = plugin_path(null, 'public/uploads/temp');
                    if(! is_dir($upload_path)){
                        @mkdir($upload_path, 0777, true);
                    }
                    $filename = $stream->save($upload_path);
                    $url = plugin_static('uploads/temp/' . $filename);
                    if(dao_config('system.upload.driver') !== 'local'){
                        if($url = Upload::instance(dao_config('system.upload'))->fetchToOss(request()->domain() . $url)){
                            @unlink($upload_path . DIRECTORY_SEPARATOR . $filename);
                        }
                    }
                    //修改数据url
                    $content['url'] = $url;
                }
            }

            if(!empty($content['url'])){
                $this->model->update([
                    'id' => $id,
                    'company_id' => $mp_info['company_id'],
                    'content' => json_encode($content, JSON_UNESCAPED_SLASHES)
                ]);
                return $this->success('success', '', ['url' => $content['url']]);
            }
            return $this->error('获取素材链接失败');
        }
    }
}